#include "utilityPredefine.h"
#include "Application.h"
#include "Camera.h"
#include "Controler.h"

Camera g_camera;
Controler g_ctrl;

Application::Application(void)
{
	displayMode = GLUT_RGB | GLUT_DOUBLE;
	wWidth = 800;
	wHeight = 600;
	wX = 100;
	wY = 100;
	title = "OpenGL";
	ctrl = &g_ctrl;
	camera = &g_camera;
}

Application::~Application(void)
{
}

void Application::init()
{
	ilInit();
	ilEnable(IL_ORIGIN_SET);

	glClearColor(0.0, 0.0, 0.0, 0.0);
	glEnable(GL_DEPTH_TEST);
	glClearDepth(1.0);
	glMatrixMode(GL_PROJECTION);
	glLoadIdentity();
	glOrtho(0.0, 1.0, 0.0, 1.0, -1.0, 1.0);
	glPolygonOffset(1.0,-1.0);
}

void Application::run()
{
	//glutInit(&argc,argv);
	glutInitDisplayMode(displayMode);
	glutInitWindowSize(wWidth,wHeight);
	glutInitWindowPosition(wX,wY);
	glutCreateWindow(title.c_str());
	GLenum err = glewInit();
	if (GLEW_OK != err)
	{
		/* Problem: glewInit failed, something is seriously wrong. */
		fprintf(stderr, "Error: %s\n", glewGetErrorString(err));
	}
	fprintf(stdout, "Status: Using GLEW %s\n", glewGetString(GLEW_VERSION));
	init();
	glutDisplayFunc(&display);
	glutReshapeFunc(&reshape);
	glutMouseFunc(&mouse);
	glutMotionFunc(&motion);
	glutKeyboardFunc(&keyboard);
	glutTimerFunc(1,&tick,0);
	glutMainLoop();
}

void Application::frame()
{

}

void Application::setDisplayMode(int glMode)
{
	displayMode = glMode;
}

void Application::setWindowSize(int width,int height)
{
	wWidth = width;
	wHeight = height;
}

void Application::setWindowPosition(int x,int y)
{
	wX = x;
	wY = y;
}

void Application::setWindowTitle(const TCHAR* title)
{
	this->title = title;
}

void Application::setControler(Controler * ctrl)
{
	this->ctrl = ctrl;
}

void Application::setCamera(Camera* camera)
{
	this->camera = camera;
}

Camera* Application::getCamera()
{
	return camera;
}

void Application::tick(int value)
{
	Application::getSingletonPtr()->frame();
	glutTimerFunc(10,&tick,0);
	glutPostRedisplay();
}

void Application::draw()
{
	camera->update();
}

void Application::display()
{
	Application::getSingletonPtr()->draw();
}

void Application::reshape(int w,int h)
{
	Application::getSingletonPtr()->wWidth = w;
	Application::getSingletonPtr()->wHeight = h;
	double aspect = (GLdouble)(w)/(h);
	glViewport(0,0,(GLsizei)(w),(GLsizei)h);
	Application::getSingletonPtr()->camera->setAspect(aspect);
	Application::getSingletonPtr()->camera->update();
}

void Application::mouse(int button, int state, int x, int y)
{
	if(Application::getSingletonPtr()->ctrl)
		Application::getSingletonPtr()->ctrl->mouse(button,state,x,y);
}

void Application::keyboard(unsigned char key, int x, int y)
{
	if(Application::getSingletonPtr()->ctrl)
		Application::getSingletonPtr()->ctrl->keyboard(key,x,y);
}

void Application::motion(int x,int y)
{
	if(Application::getSingletonPtr()->ctrl)
		Application::getSingletonPtr()->ctrl->motion(x,y);
}